<?php

namespace app\services;

use app\traits\Page;
use plugin\admin\app\model\Goods;
use plugin\admin\app\model\Order;
use plugin\admin\app\model\PrizeDrawActivity;
use plugin\admin\app\model\PrizeDrawActivityGood;
use plugin\admin\app\model\PrizeDrawGood;
use plugin\admin\app\model\UserPrizeDraw;

class UserPrizeDrawService
{
    public static function waitOpenList($page = 1, $length = 10)
    {
        $offset = ($page - 1) * $length;

        $query = UserPrizeDraw::select(['order_no', 'aid', 'pid', 'number', 'created_time'])->where('user_id', get_user_id())->where('status', UserPrizeDraw::STATUS_WAIT);

        $totalCount = (clone $query)->count();
        $list = (clone $query)->offset($offset)->limit($length)->get()->toArray();

        $activityIds = array_column($list, 'aid');
        $activities = PrizeDrawActivity::select(['id', 'pid', 'target_count', 'sale_count', 'fake_process', 'fake_sale_count', 'loop_count', 'name', 'status'])->whereIn('id', $activityIds)->get()->keyBy('id')->toArray();

        $pids = array_column($list, 'pid');
        $goodsList = Goods::select(['id', 'name', 'thumb'])->whereIn('id', $pids)->get()->keyBy('id')->toArray();

        foreach ($list as $k=>$v) {
            $activity = $activities[$v['aid']];
            PrizeDrawService::processData($activity);

            $goods = $goodsList[$v['pid']];
            $goods['thumb'] = full_url($goods['thumb']);

            $activity['goods_info'] = $goods;

            $list[$k]['activity'] = $activity;

        }

        return Page::wrap($totalCount, $page, $length, $list);
    }

    public static function prizeDrawList($page = 1, $length = 10)
    {
        $offset = ($page - 1) * $length;

        $query = UserPrizeDraw::select(['order_no', 'aid', 'pid', 'status', 'number', 'created_time'])->where('user_id', get_user_id());

        $totalCount = (clone $query)->count();
        $list = (clone $query)->offset($offset)->limit($length)->get()->toArray();

        $activityIds = array_column($list, 'aid');
        $activities = PrizeDrawActivity::select(['id', 'pid', 'goods_info', 'target_count', 'sale_count', 'status', 'fake_process', 'fake_sale_count', 'loop_count', 'name'])->whereIn('id', $activityIds)->get()->keyBy('id')->toArray();


        $prizeDrawActivityGoodsList = PrizeDrawActivityGood::whereIn('prize_draw_activity_id', $activityIds)->get()->toArray();

        $pids = array_column($list, 'pid');
        $goodsList = Goods::select(['id', 'name', 'thumb'])->whereIn('id', $pids)->get()->keyBy('id')->toArray();

        foreach ($list as $k=>$v) {
            $activity = $activities[$v['aid']];
            PrizeDrawService::processData($activity);

            if ($v['status'] == UserPrizeDraw::STATUS_WAIT) {
                $goods = $goodsList[$v['pid']];
            } else {

                $tempGoods = [];
                foreach ($prizeDrawActivityGoodsList as $goods) {
                    if ($goods['prize_draw_activity_id'] == $v['aid'] && $goods['goods_id'] == $v['pid']) {
                        $tempGoods = json_decode($goods['goods_info'], true);
                        break;
                    }
                }

                $goods = [
                    'id' => $tempGoods['id'] ?? '',
                    'name' => $tempGoods['name'] ?? '',
                    'thumb' => $tempGoods['thumb'] ?? '',
                ];
            }

            $goods['thumb'] = full_url($goods['thumb']);

            $activity['goods_info'] = $goods;
            $list[$k]['activity'] = $activity;
            $list[$k]['status_text'] = UserPrizeDraw::getStatusText($v['status']);
        }

        return Page::wrap($totalCount, $page, $length, $list);
    }

    public static function winList($page = 1, $length = 10)
    {
        $offset = ($page - 1) * $length;

        $query = UserPrizeDraw::select(['order_no', 'aid', 'pid', 'status', 'order_status', 'number', 'level', 'created_time'])->where('user_id', get_user_id())->where('status', UserPrizeDraw::STATUS_WIN);

        $totalCount = (clone $query)->count();
        $list = (clone $query)->offset($offset)->limit($length)->get()->toArray();

        $activityIds = array_column($list, 'aid');
        $activities = PrizeDrawActivity::select(['id', 'pid', 'goods_info', 'target_count', 'sale_count', 'status', 'fake_process', 'fake_sale_count', 'loop_count', 'name'])->whereIn('id', $activityIds)->get()->keyBy('id')->toArray();

        $prizeDrawGoodsList = PrizeDrawGood::whereIn('aid', $activityIds)->get()->toArray();

        $prizeDrawActivityGoodsList = PrizeDrawActivityGood::whereIn('prize_draw_activity_id', $activityIds)->get()->keyBy('goods_id')->toArray();

        foreach ($list as $k=>$v) {
            $activity = $activities[$v['aid']];
            PrizeDrawService::processData($activity);

            $tempGoods = json_decode($prizeDrawActivityGoodsList[$v['pid']]['goods_info'], true);
            $goods = [
                'id' => $tempGoods['id'],
                'name' => $tempGoods['name'],
                'thumb' => $tempGoods['thumb'],
            ];

            $goods['thumb'] = full_url($goods['thumb']);

            $winGoods = [];
            foreach ($prizeDrawGoodsList as $goodsItem) {
                if ($v['level'] == $goodsItem['level'] && $v['aid'] == $goodsItem['aid']) {
                    $winGoods = json_decode($goodsItem['goods_info'], true);
                    break;
                }
            }

            $activity['goods_info'] = $goods;
            $list[$k]['prize_draw_goods_info'] = [
                'name' => $winGoods['name'] ?? '',
                'thumb' => full_url($winGoods['thumb'] ?? ''),
                'count' => 1,
                'price' => $winGoods['price'] ?? 0
            ];

            $list[$k]['level_text'] = PrizeDrawGood::getLevelText($v['level']);
            $list[$k]['activity'] = $activity;
            $list[$k]['status_text'] = UserPrizeDraw::getStatusText($v['status']);
            $list[$k]['order_status_text'] = UserPrizeDraw::getOrderStatusText($v['order_status']);
        }

        return Page::wrap($totalCount, $page, $length, $list);
    }

    public static function orderDetail($orderNo)
    {
        $item = UserPrizeDraw::select(['order_no', 'aid', 'status', 'order_status', 'number', 'address_info', 'name', 'reject_reason', 'idcard', 'level', 'created_time', 'shipping_time', 'receive_time', 'express_no', 'express_company'])->where('user_id', get_user_id())->where('order_no', $orderNo)->first();

        $activity = PrizeDrawActivity::select(['id', 'pid', 'goods_info', 'target_count', 'sale_count', 'open_time', 'status', 'fake_process', 'fake_sale_count', 'loop_count', 'name'])->where('id', $item['aid'])->first()->toArray();

        $prizeDrawGoodsList = PrizeDrawGood::where('aid', $item['aid'])->get()->toArray();

        $prizeDrawActivityGoods = PrizeDrawActivityGood::where('prize_draw_activity_id', $activity['id'])->first()->toArray();

        PrizeDrawService::processData($activity);

        $tempGoods = json_decode($prizeDrawActivityGoods['goods_info'], true);
        $goods = [
            'id' => $tempGoods['id'],
            'name' => $tempGoods['name'],
            'thumb' => $tempGoods['thumb'],
        ];

        $goods['thumb'] = full_url($goods['thumb']);

        $winGoods = [];
        foreach ($prizeDrawGoodsList as $goodsItem) {
            if ($item['level'] == $goodsItem['level'] && $item['aid'] == $goodsItem['aid']) {
                $winGoods = json_decode($goodsItem['goods_info'], true);
                break;
            }
        }

        $activity['goods_info'] = $goods;
        $item['prize_draw_goods_info'] = [
            'name' => $winGoods['name'] ?? '',
            'thumb' => full_url($winGoods['thumb'] ?? ''),
            'count' => 1,
            'price' => $winGoods['price'] ?? 0
        ];
        $item['activity'] = $activity;
        $item['address_info'] = json_decode($item['address_info'], true);
        $item['level_text'] = PrizeDrawGood::getLevelText($item['level']);
        $item['status_text'] = UserPrizeDraw::getStatusText($item['status']);
        $item['order_status_text'] = UserPrizeDraw::getOrderStatusText($item['order_status']);

        return $item;
    }

    public static function confirm($orderNo)
    {
        $order = UserPrizeDraw::where('user_id', get_user_id())->where('order_no', $orderNo)->first();

        if (!$order) {
            throw new \Exception('不存在的订单');
        }

        if ($order['order_status'] != UserPrizeDraw::ORDER_STATUS_WAIT_RECEIVE) {
            throw new \Exception('该订单无法确认收货');
        }

        $order->order_status = UserPrizeDraw::ORDER_STATUS_FINISH;
        $order->receive_time = date('Y-m-d H:i:s');
        $order->save();
    }

    public static function finishReceiveInfo($orderNo, $addressId, $data)
    {
        $res = UserPrizeDraw::where('user_id', get_user_id())->where('order_no', $orderNo)->first();

        if (!$res) {
            throw new \Exception('不存在的记录');
        }

        if ($res['order_status'] != UserPrizeDraw::ORDER_STATUS_WAIT_FINISH && $res['order_status'] != UserPrizeDraw::ORDER_STATUS_AUDIT_FAIL) {
            throw new \Exception('该状态不允许修改');
        }

        $addressInfo = AddressService::detail($addressId);
        $res->address_info = json_encode($addressInfo, JSON_UNESCAPED_UNICODE);
        $res->name = $data['name'];
        $res->idcard = $data['idcard'];
        $res->order_status = UserPrizeDraw::ORDER_STATUS_AUDIT;
        $res->save();
    }

    public static function add($aid, $uid, $orderNo, $goodsId, $buyCount)
    {
        UserPrizeDraw::insert([
            'aid' => $aid,
            'user_id' => $uid,
            'pid' => $goodsId,
            'buy_count' => $buyCount,
            'relation_order_no' => $orderNo,
            'order_no' => self::generateOrderNo(),
            'created_time' => date('Y-m-d H:i:s'),
            'number' => self::generateNumber($aid),
            'status' => UserPrizeDraw::STATUS_WAIT,
            'order_status' => UserPrizeDraw::ORDER_STATUS_WAIT_FINISH,
        ]);

    }

    public static function generateOrderNo()
    {
        return 'CJ' . substr(str_shuffle("0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZ"), 0, 11) . mt_rand(1000, 9999);
    }

    public static function generateNumber($aid)
    {
        $activity = PrizeDrawActivity::where('id', $aid)->first();

        $list = UserPrizeDraw::where('aid', $aid)->get()->toArray();
        $numbers = array_column($list, 'number');

        $min = 1;
        $max = $activity['target_count'] * 100;

        while (in_array($number = mt_rand($min, $max), $numbers)) {
            continue;
        }

        return $number;
    }
}